package com.jikangjun.disk.file.controller;

import com.alibaba.fastjson.JSON;
import com.jikangjun.disk.file.entity.FileEntity;
import com.jikangjun.disk.file.entity.FileShareEntity;
import com.jikangjun.disk.file.entity.SearchFileEntity;
import com.jikangjun.disk.file.service.FileloService;
import com.jikangjun.disk.file.service.FileService;
import com.jikangjun.disk.mybatis.entity.PtFileEntity;
import com.jikangjun.disk.mybatis.flexigrid.PagingEntity;
import com.jikangjun.disk.mybatis.flexigrid.TblResponseEntity;
import com.jikangjun.disk.spring.control.BaseController;
import com.jikangjun.disk.spring.security.UserDiskEntity;
import org.apache.tomcat.util.net.openssl.ciphers.Authentication;
import org.springframework.http.ResponseEntity;
import org.springframework.security.access.annotation.Secured;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Controller;
import org.springframework.stereotype.Service;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.annotation.Resource;
import java.io.IOException;
import java.util.List;
import java.util.ArrayList;
import java.util.Map;
import java.util.HashMap;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.FileInputStream;
import org.springframework.context.MessageSource;
import org.springframework.context.i18n.LocaleContextHolder;

import java.io.OutputStream;
import java.net.URLEncoder;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import com.jikangjun.disk.file.entity.FileCopyRequest;
import com.jikangjun.disk.file.entity.FileMoveRequest;
import com.jikangjun.disk.recycle.service.RecycleService;
import org.springframework.web.multipart.MultipartHttpServletRequest;

/**
 * 文件管理控制器，处理文件相关的所有HTTP请求
 * 包括文件上传、下载、复制、移动、重命名、删除等操作
 */
@Controller
@RequestMapping("/file")
public class FileController extends BaseController {
    private static final Logger logger = LoggerFactory.getLogger(FileController.class);
    
    @Resource
    private FileloService fileIoService;  // 文件IO服务，处理文件物理存储操作

    @Resource
    private FileService fileService;  // 文件业务服务，处理文件元数据操作

    @Resource
    private RecycleService recycleService;  // 回收站服务，处理文件删除到回收站操作
    
    @Resource
    private MessageSource messageSource;  // 国际化消息源


    @RequestMapping("/fileAll")
    public String fileAll(){
        return "file/filePage";
    }

    // 注释掉分享相关方法
    // @RequestMapping("/queryMyShareList")
    // @ResponseBody
    // public String queryMyShareList(){
    //     // TODO: 实现查询我的分享列表的逻辑
    //     return successJson("share.query.success");
    // }

    // @RequestMapping("/getShareLink")
    // @ResponseBody
    // public String getShareLink(){
    //     // TODO: 实现获取分享链接的逻辑
    //     return successJson("share.copy.success");
    // }

    // @RequestMapping("/queryShareById")
    // @ResponseBody
    // public String queryShareById(){
    //     // TODO: 实现根据ID查询分享信息的逻辑
    //     return successJson("share.query.success");
    // }

    // @RequestMapping("/updateShare")
    // @ResponseBody
    // public String updateShare(){
    //     // TODO: 实现更新分享信息的逻辑
    //     return successJson("share.update.success");
    // }

    // @RequestMapping("/cancelShare")
    // @ResponseBody
    // public String cancelShare(){
    //     // TODO: 实现取消分享的逻辑
    //     return successJson("share.cancel.success");
    // }

    // @RequestMapping("/deleteShare")
    // @ResponseBody
    // public String deleteShare(){
    //     // TODO: 实现删除分享记录的逻辑
    //     return successJson("share.delete.success");
    // }

    // @RequestMapping("/cancelShareBatch")
    // @ResponseBody
    // public String cancelShareBatch(){
    //     // TODO: 实现批量取消分享的逻辑
    //     return successJson("share.cancel.batch.success");
    // }

    // @RequestMapping("/deleteShareBatch")
    // @ResponseBody
    // public String deleteShareBatch(){
    //     // TODO: 实现批量删除分享记录的逻辑
    //     return successJson("share.delete.batch.success");
    // }

    @GetMapping("/file/browser")
    public String fileBrowser() {
        // 后续可添加文件数据查询逻辑
        return "file/fileBrowser";
    }

    @RequestMapping("/syncFileData")
    @ResponseBody
    public String syncFileData(){
        fileIoService.syncFileData();
        return successJson("file.sync.data.success");
    }

    /**
     * 处理文件上传请求
     * @param request 包含上传文件的Multipart请求
     * @param parentId 文件要上传到的父目录ID
     * @return JSON格式的成功/失败响应
     * @throws IOException 如果文件读写发生错误
     */
    @RequestMapping("/uploadFile")
    @ResponseBody
    public String uploadFile(MultipartHttpServletRequest request, @RequestParam("parentId") String parentId) throws IOException {
        // 从请求中获取上传的文件
        MultipartFile multipartFile = request.getFile("fileName");
        String fileName = multipartFile.getOriginalFilename();

        // 调用文件IO服务处理上传
        fileIoService.uploadFile(parentId, fileName, multipartFile.getInputStream());

        // 返回上传成功响应
        return successJson("file.upload.success");
    }


    /**
     * 浏览个人文件页面
     */
    @RequestMapping("/myFiles")
    public String myFiles(@RequestParam(value = "parentId", required = false) String parentId,
                          Model model) {
        // 获取当前登录用户
        UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                .getAuthentication().getPrincipal();
        String userId = user.getUserUuid();

        // 获取当前目录下的文件列表
        List<FileEntity> fileList = fileService.getUserFiles(userId, parentId);
        model.addAttribute("fileList", fileList);
        model.addAttribute("currentParentId", parentId);
        return "file/myFilesPage";
    }

    // 注释掉共享文件页面方法
    // /**
    //  * 浏览共享文件页面
    //  */
    // @RequestMapping("/sharedFiles")
    // public String sharedFiles(Model model) {
    //     UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
    //             .getAuthentication().getPrincipal();
    //     String userId = user.getUserUuid();
    //
    //     List<FileShareEntity> sharedList = fileService.getSharedFiles(userId);
    //     model.addAttribute("sharedList", sharedList);
    //     return "file/sharedFilesPage";
    // }
    /**
     * 分页查询文件信息列表
     * @param entity 包含查询条件的SearchFileEntity对象
     * @param paging 分页信息对象
     * @return JSON格式的分页查询结果
     */
    @RequestMapping("/queryFileInfoListByPage")
    @ResponseBody
    public String queryFileInfoListByPage(SearchFileEntity entity, PagingEntity paging){

        TblResponseEntity<PtFileEntity> tblResponseEntity = fileService.queryFileInfoListByPage(entity,paging);
        return JSON.toJSONString(tblResponseEntity);
    }


    /**
     * 创建新文件夹
     */
    /**
     * 创建新文件夹
     * @param folderName 新文件夹名称
     * @param parentId 父文件夹ID(可选，为空时创建在根目录)
     * @return JSON格式的成功/失败响应
     */
    @RequestMapping("/createFolder")
    @ResponseBody
    public String createFolder(@RequestParam("folderName") String folderName,
                               @RequestParam(value = "parentId", required = false) String parentId) {
        try {
            UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                    .getAuthentication().getPrincipal();

            FileEntity folder = new FileEntity();
            folder.setFileId(java.util.UUID.randomUUID().toString().replace("-", ""));
            folder.setFileName(folderName);
            folder.setUserId(user.getUserUuid());
            folder.setParentId(parentId);
            folder.setIsFolder(1); // 1表示文件夹
            folder.setCreateTime(new java.util.Date());
            folder.setUpdateTime(new java.util.Date());

            fileService.createFolder(folder);
            return successJson("folder.create.success");
        } catch (Exception e) {
            return failJson("folder.create.fail");
        }
    }


    /**
     * 重命名文件
     */
    /**
     * 重命名文件(需要ROLE_cldk_file_rename权限)
     * @param fileId 要重命名的文件ID
     * @param newName 新的文件名
     * @return JSON格式的成功/失败响应
     */
    @Secured("ROLE_cldk_file_rename")
    @PostMapping("/rename")
    @ResponseBody
    public String renameFile(@RequestParam("fileId") String fileId, 
                            @RequestParam("newName") String newName) {
        try {
            UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                    .getAuthentication().getPrincipal();
            String userId = user.getUserUuid();

            fileService.renameFile(fileId, newName, userId);
            return successJson("file.rename.success");
        } catch (Exception e) {
            logger.error("文件重命名失败", e);
            return failJson("file.rename.fail");
        }
    }

    /**
     * 下载文件
     */
    /**
     * 处理文件下载请求
     * @param fileUuid 要下载的文件唯一标识符
     * @return ResponseEntity包含文件字节数组和HTTP头信息
     *         包括Content-Type、Content-Disposition等
     */
    @RequestMapping("/downFile/{fileUuid}")
    @ResponseBody
    public ResponseEntity<byte[]> downFile(@PathVariable("fileUuid") String fileUuid){
        // 调用文件IO服务获取文件内容和响应头
        ResponseEntity<byte[]> responseEntity = fileIoService.downFile(fileUuid);
        return responseEntity;
    }

    /**
     * 复制文件
     */
    /**
     * 复制文件(支持批量操作)
     * @param sourceFileId 要复制的文件ID(多个文件用逗号分隔)
     * @param targetDirectoryId 目标目录ID
     * @return JSON格式的成功/失败响应
     */
    @PostMapping("/copy")
    @ResponseBody
    public String copyFile(@RequestParam("sourceFileId") String sourceFileId,
                          @RequestParam("targetDirectoryId") String targetDirectoryId) {
        try {
            UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                    .getAuthentication().getPrincipal();
            String userId = user.getUserUuid();

            // 支持批量复制
            String[] fileIds = sourceFileId.split(",");
            for (String fileId : fileIds) {
                FileCopyRequest request = new FileCopyRequest();
                request.setSourceFileId(fileId.trim());
                request.setTargetDirectoryId(targetDirectoryId);
                request.setUserId(userId);

                fileService.copyFile(request);
            }
            return successJson("file.copy.success");
        } catch (Exception e) {
            logger.error("文件复制失败", e);
            return failJson("file.copy.fail");
        }
    }

    /**
     * 剪切文件
     */
    /**
     * 剪切/移动文件(支持批量操作)
     * @param sourceFileId 要剪切的文件ID(多个文件用逗号分隔)
     * @param targetDirectoryId 目标目录ID
     * @return JSON格式的成功/失败响应
     */
    @PostMapping("/cut")
    @ResponseBody
    public String cutFile(@RequestParam("sourceFileId") String sourceFileId,
                         @RequestParam("targetDirectoryId") String targetDirectoryId) {
        try {
            UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                    .getAuthentication().getPrincipal();
            String userId = user.getUserUuid();

            // 支持批量剪切
            String[] fileIds = sourceFileId.split(",");
            for (String fileId : fileIds) {
                FileMoveRequest request = new FileMoveRequest();
                request.setSourceFileId(fileId.trim());
                request.setTargetDirectoryId(targetDirectoryId);
                request.setUserId(userId);

                fileService.moveFile(request);
            }
            return successJson("file.cut.success");
        } catch (Exception e) {
            logger.error("文件剪切失败", e);
            return failJson("file.cut.fail");
        }
    }

    /**
     * 检查文件冲突
     */
    @PostMapping("/checkConflict")
    @ResponseBody
    public String checkConflict(@RequestParam("fileIds") String fileIds,
                               @RequestParam("targetDirectoryId") String targetDirectoryId,
                               @RequestParam("operation") String operation) {
        try {
            UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                    .getAuthentication().getPrincipal();
            String userId = user.getUserUuid();

            List<String> conflicts = new ArrayList<>();
            String[] fileIdArray = fileIds.split(",");
            
            for (String fileId : fileIdArray) {
                FileEntity sourceFile = fileService.getFileDetail(fileId.trim());
                if (sourceFile != null) {
                    // 检查目标目录中是否存在同名文件
                    boolean exists = fileService.checkFileExists(sourceFile.getFileName(), targetDirectoryId);
                    if (exists) {
                        conflicts.add(sourceFile.getFileName());
                    }
                }
            }

            Map<String, Object> result = new HashMap<>();
            result.put("success", true);
            result.put("conflicts", conflicts);
            return JSON.toJSONString(result);
        } catch (Exception e) {
            logger.error("检查文件冲突失败", e);
            return failJson("file.conflict.check.fail");
        }
    }

    /**
     * 粘贴文件
     */
    @PostMapping("/paste")
    @ResponseBody
    public String pasteFile(@RequestParam("fileIds") String fileIds,
                           @RequestParam("targetDirectoryId") String targetDirectoryId,
                           @RequestParam("operation") String operation,
                           @RequestParam("conflictAction") String conflictAction) {
        try {
            UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                    .getAuthentication().getPrincipal();
            String userId = user.getUserUuid();

            String[] fileIdArray = fileIds.split(",");
            int successCount = 0;
            int skipCount = 0;

            for (String fileId : fileIdArray) {
                try {
                    FileEntity sourceFile = fileService.getFileDetail(fileId.trim());
                    if (sourceFile == null) {
                        continue;
                    }

                    // 检查目标目录中是否存在同名文件
                    boolean exists = fileService.checkFileExists(sourceFile.getFileName(), targetDirectoryId);
                    
                    if (exists) {
                        if ("skip".equals(conflictAction)) {
                            skipCount++;
                            continue;
                        } else if ("overwrite".equals(conflictAction)) {
                            // 注意：这里需要实现删除同名文件的逻辑
                            // 暂时跳过删除逻辑，因为需要更复杂的查询来找到具体的文件
                        }
                    }

                    if ("copy".equals(operation)) {
                        // 执行复制操作
                        FileCopyRequest copyRequest = new FileCopyRequest();
                        copyRequest.setSourceFileId(fileId.trim());
                        copyRequest.setTargetDirectoryId(targetDirectoryId);
                        copyRequest.setUserId(userId);
                        fileService.copyFile(copyRequest);
                    } else if ("cut".equals(operation)) {
                        // 执行剪切操作
                        FileMoveRequest moveRequest = new FileMoveRequest();
                        moveRequest.setSourceFileId(fileId.trim());
                        moveRequest.setTargetDirectoryId(targetDirectoryId);
                        moveRequest.setUserId(userId);
                        fileService.moveFile(moveRequest);
                    }
                    
                    successCount++;
                } catch (Exception e) {
                    logger.error("处理文件失败: " + fileId, e);
                }
            }

            // 构建国际化消息
            if (successCount > 0) {
                // 有成功的文件
                if ("copy".equals(operation)) {
                    return successJson("file.copy.success.count", successCount);
                } else {
                    return successJson("file.move.success.count", successCount);
                }
            } else if (skipCount > 0) {
                // 只有跳过的文件
                return successJson("file.skip.conflict.count", skipCount);
            } else {
                // 默认成功消息
                return successJson("file.paste.success");
            }
        } catch (Exception e) {
            logger.error("文件粘贴失败", e);
            return failJson("file.paste.fail");
        }
    }

    // 注释掉分享文件相关方法
    // /**
    //  * 分享文件
    //  */
    // @PostMapping("/doShare")
    // @ResponseBody
    // public String doShare(@RequestParam("fileId") String fileId,
    //                      @RequestParam(value = "expireTime", required = false) String expireTime) {
    //     try {
    //         UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
    //                 .getAuthentication().getPrincipal();
    //         String userId = user.getUserUuid();
    //
    //         // 检查文件是否存在
    //         FileEntity file = fileService.getFileDetail(fileId);
    //         if (file == null) {
    //             return failJson("file.not.exist");
    //         }
    //
    //         // 检查权限
    //         if (!file.getUserId().equals(userId)) {
    //             return failJson("file.no.permission");
    //         }
    //
    //         // TODO: 实现分享逻辑
    //         // 这里可以调用分享服务来创建分享链接
    //         // 暂时返回成功
    //         return successJson("share.success");
    //     } catch (Exception e) {
    //         logger.error("文件分享失败", e);
    //         return failJson("share.fail");
    //     }
    // }

    /**
     * 删除文件到回收站
     */
    /**
     * 删除文件到回收站(需要ROLE_cldk_file_del权限)
     * @param fileIds 要删除的文件ID(多个文件用逗号分隔)
     * @return JSON格式的成功/失败响应
     */
    @Secured("ROLE_cldk_file_del")
    @PostMapping("/deleteToRecycle")
    @ResponseBody
    public String deleteToRecycle(@RequestParam("fileIds") String fileIds) {
        try {
            UserDiskEntity user = (UserDiskEntity) SecurityContextHolder.getContext()
                    .getAuthentication().getPrincipal();
            String userId = user.getUserUuid();

            // 支持批量删除
            String[] fileIdArray = fileIds.split(",");
            for (String fileId : fileIdArray) {
                fileId = fileId.trim();
                if (!fileId.isEmpty()) {
                    // 检查文件是否存在
                    FileEntity file = fileService.getFileDetail(fileId);
                    if (file != null && file.getUserId().equals(userId)) {
                        // 将文件移动到回收站
                        fileService.moveToRecycle(fileId, userId);
                    }
                }
            }
            return successJson("file.delete.to.recycle.success");
        } catch (Exception e) {
            logger.error("删除文件到回收站失败", e);
            return failJson("file.delete.to.recycle.fail");
        }
    }
    /**
     * 根据文件ID查询文件详细信息
     * @param fileUuid 文件唯一标识符
     * @return JSON格式的文件信息
     */
    @RequestMapping("/queryFileInfoById")
    @ResponseBody
    public String queryFileInfoById(@RequestParam("fileUuid") String fileUuid){
        PtFileEntity ptFileEntity =fileService.queryFileInfoById(fileUuid);
        return JSON.toJSONString(ptFileEntity);
    }

    /**
     * 生成文件分享链接
     * @param fileUuid 要分享的文件唯一标识符
     * @param fileValidity 链接有效期(天数)
     * @return JSON格式的成功/失败响应，包含分享链接
     */
    @RequestMapping("/queryShareUrl")
    @ResponseBody
    public String queryShareUrl(@RequestParam("fileUuid") String fileUuid,@RequestParam("fileValidity") Integer fileValidity){
        try {
            String url = fileIoService.queryShareUrl(fileUuid,fileValidity);
            if (url != null && !url.isEmpty()) {
                logger.info("分享链接生成成功: fileUuid={}, validity={}天", fileUuid, fileValidity);
                return successJson("file.share.success", url);
            } else {
                logger.error("分享链接生成失败: fileUuid={}, validity={}天", fileUuid, fileValidity);
                return failJson("file.share.fail");
            }
        } catch (Exception e) {
            logger.error("分享链接生成异常: fileUuid={}, validity={}天", fileUuid, fileValidity, e);
            return failJson("file.share.fail");
        }
    }

}
